<?php

/**
 * 百大-海恒达SDK
 * @author chenyun
 */
namespace App\Service\VendorClient\ShophaihengdaApi;
use App\Service\Code\Normal;
use App\Service\TaskServer\TaskWorker;
use Service\AppService\IdService;

class ShophaihengdaApiClient
{
    private $account  = 'shophaihengda';
    protected $config;
    /**
     * 初始参数
     * @param obj $collection
     */
    public function __construct( $apiBody = [] ) 
    {
        $this->config = $apiBody;
    }
    
    /**
     * 创建订单
     */
    public function createOrder( $params = [] ) 
    {   
        ini_set('serialize_precision', 16);
        
        if( empty($params['supplierOrder']) || empty($params['orderGoods']) || empty($params['order']) || empty($params['binfo']) ) {
            return Normal::returnCode(Normal::FAIL,"except param supplierOrder or orderGoods or order or binfo");
        }
        //组装订单参数
        $orderInfo = $params['supplierOrder'];
        $order     = $params['order'];
        $binfo     = $params['binfo'];
        //运费
        $deliver_money  = $orderInfo['deliver_money'];

        $hscode_map_list     = $params['hscode_map_list'];
        //商品下单组
        $orderList = [];
        $productAmt = $TaxAmt = 0 ;
        foreach ($params['orderGoods'] as $key => $item )
        {
            //卖价
            $price              = $item['price'];
            //商品购买规格数量
            $spec_num           = $item['spec_num'];
            //商品购买数量(下单数量 X 起售数量)
            $quantity           = $item['quantity'];
            //实际购买数量
            $buyAcount          = $spec_num * $quantity ;
            //如果商品除不尽，得多取以为，减去实际金额为折扣，折扣不能为负数
            if( $key == 0 ) {
                $singleDeliveryMoney = bcdiv((string)$deliver_money,(string)$quantity,3);
                $singleDeliveryMoney = bcmul((string)$singleDeliveryMoney,(string)100,1);
                $singleDeliveryMoney = bcdiv((string)ceil($singleDeliveryMoney), (string)100,2);
                $price               = bcadd((string)$price, (string)$singleDeliveryMoney,2);
            }
            //单个商品价格
            $singleGoodsPrice   = bcdiv((string)$price, (string)$spec_num,3);
            $singleGoodsPrice   = ceil(bcmul((string)$singleGoodsPrice,(string)'100',1));
            $singleGoodsPrice   = bcdiv((string)$singleGoodsPrice,'100',2);
            $totalGoods         = bcmul((string)$singleGoodsPrice,(string)$buyAcount,2);

            //含税税率
            $tax_rate           = bcadd('1', (string)$item['tax_rate'],4);
            //不含税价格
            $not_tax_price      = bcdiv((string)$singleGoodsPrice, (string)$tax_rate,3);
            // echo "含税税率:".$tax_rate."不含税价格：".$not_tax_price;
            $not_tax_price      = ceil(bcmul((string)$not_tax_price,(string)'100',1));
            // echo "含税税率:".$tax_rate."不含税价格：".$not_tax_price;
            $not_tax_price      = bcdiv((string)$not_tax_price,'100',2);
            //税金
            $singleGoodsTax     = bcsub((string)$singleGoodsPrice, (string)$not_tax_price,3);
            //单个商品总税金
            $totalGoodsTax  = bcmul((string)$singleGoodsTax,(string)$buyAcount,2);
            //单个商品总不含税价格
            $totalGoods     = bcmul((string)$not_tax_price,(string)$buyAcount,2);
            //获取商品hscode信息
            if(empty($hscode_map_list[$item['supplier_skucode']])){
                return Normal::returnCode(Normal::FAIL,"供应商商品ID".$item['supplier_skuid']."的hscode信息不存在，请核实！");
            }
            
            $hscodeInfo = $hscode_map_list[$item['supplier_skucode']];
            
            //netweight = qty1 = netWeight / 1000 *购买数量
            $NetWeight = $hscodeInfo["NetWeight"];
            $netWeight = bcdiv((float)$NetWeight,1000,2);
            $netWeight = $qty1 = bcmul((float)$netWeight,(float)$buyAcount,2);
            
            //Weight  = GrossWeight/1000*购买数
            $GrossWeight = $hscodeInfo["GrossWeight"];
            $weight = bcdiv((float)$GrossWeight,1000,2);
            $weight = bcmul((float)$weight,(float)$buyAcount,2);

            //商品组
            $orderList[] = [
                'barCode'           => $item["barcode"],
                'ciqbarcode'        => $hscodeInfo["Code"],
                'country'           => $hscodeInfo["Country"],
                'currency'          => $hscodeInfo["Current"],
                'itemDescribe'      => "",
                'itemName'          => $hscodeInfo["Name"],
                'itemNo'            => $item["supplier_skucode"],
                'netweight'         => $netWeight,
                'note'              => "",
                'price'             => (float)$not_tax_price,
                'qty'               => (int)$buyAcount,
                'qty1'              => $qty1,
                'specifications'    => $hscodeInfo["Specifications"],
                'totalPrice'        => (float)$totalGoods,
                'unit'              => $hscodeInfo["Unit"],
                'unit1'             => $hscodeInfo["UnitCode"],
                'unit2'             => $hscodeInfo["SecondUnitCode"],
                'weight'            => $weight,
            ];
            $productAmt = bcadd((string)$productAmt,(string)$totalGoods,2);
            $TaxAmt     = bcadd((string)$TaxAmt,(string)$totalGoodsTax,2);
        }
        //实际下单金额
        $real_total_money   = $orderInfo['real_total_money'];
        //订单总金额 = 含税商品总金额 + 运费 - 优惠金额
        $ActualPaidAmt = bcadd((string)$productAmt,(string)$TaxAmt,2);
        //优惠金额
        $discount_money = bcsub((string)$ActualPaidAmt,$real_total_money,2);
        
        //下单支付的时候支付信息
        $apply_extends  = @json_decode($orderInfo['apply_extends'],true);
        
        //支付时间
        $payTime        = empty($order['payTime']) ? $orderInfo['pay_time'] :$order['payTime'];
        //支付时间
        $pay_time       = $payTime ? $payTime : time();
        $pay_time       = date('Y-m-d H:i:s',$pay_time);
        
        //支付流水号
        $pay_sn         = $order['paySerial']??$orderInfo['pay_sn'];
        
        //获取上游供应商支付方式路由
        $payCommanyCode = $apply_extends['payCommanyCode'] ?? '';
        $PayCompanyCode = $order['payCommanyCode'] ? $order['payCommanyCode'] : $payCommanyCode;
        $PayCommanyName = $apply_extends['payCommanyName'] ?? '';
        $PayCommanyName = $order['payCommanyName'] ? $order['payCommanyName'] : $PayCommanyName;
        
        //电商平台信息
        $enterpriseNum = $apply_extends['enterpriseNum'] ?? '';
        $enterpriseName = $apply_extends['enterpriseName'] ?? '';
        $enterpriseNum = $order['enterpriseNum'] ? $order['enterpriseNum'] : $enterpriseNum;
        $enterpriseName = $order['enterpriseName'] ? $order['enterpriseName'] : $enterpriseName;
        
        //创建订单数据
       $orderHead = [
            'acturalPaid'       => (float)$real_total_money,
            'assureCode'        => $this->config['assureCode'],
            'batchNumbers'      => '',
            'billmode'          => $this->config['billmode'],
            'buyerIdNumber'     => $orderInfo['buyer_idcard'],
            'buyerIdType'       => '1',
            'buyerName'         => $orderInfo['buyer_realname'],
            'buyerRegNo'        => $orderInfo['buyer_phone'],
            'consignee'         => $orderInfo['receive_name'],
            'consigneeAddress'  => $orderInfo['province'].$orderInfo['city'].$orderInfo['district'].$orderInfo['receive_address'],
            'consigneeTelephone'=> $orderInfo['recveive_phone'],
            'consigneecity'     => $orderInfo['city'],
            'consigneecountry'  => '中国',
            'consigneedistrict' => $orderInfo['district'],
            'consigneeprov'     => $orderInfo['province'],
            'currency'          => '142',
            'discount'          => (float)$discount_money,
            'ebcCode'           => $enterpriseNum,
            'ebcName'           => $enterpriseName,
            'ebpCode'           => $enterpriseNum,
            'ebpName'           => $enterpriseName,
            'freight'           => 0.00,
            'goodsValue'        => (float)$productAmt,
            'note'              => $orderInfo['order_remark'] ? $orderInfo['order_remark'] : '请尽快发货',
            'orderNo'           => $orderInfo['supplier_dsn'],
            'orderType'         => 'I',
            'payCode'           => $PayCompanyCode,
            'payName'           => $PayCommanyName,
            'payTrCsactionId'   => $pay_sn,
            'quantity'          => 1,
            'senderuseraddress' => $this->config["senderuseraddress"],
            'senderusercity'    => $this->config["senderusercity"],
            'senderusercountry' => $this->config["senderusercountry"],
            'senderuserdistrict'=> $this->config["senderuserdistrict"],
            'senderusername'    => $this->config["senderusername"],
            'senderuserprov'    => $this->config["senderuserprov"],
            'senderusertelephone'=> $this->config["senderusertelephone"],
            'taxTotal'          => (float)$TaxAmt
        ];
        $data = [
            'orderHead' => $orderHead,
            'orderList' => $orderList,
        ];
        $requestParam = [
            'method'    => 'createOrder',
            'data'      => [
                'companyCode'   => $this->config["companyCode"],
                'msgType'       => "Order",
                'data'          => json_encode($data,JSON_UNESCAPED_UNICODE),
                'CheckCode'     => $this->getSign($data),
            ]
        ];
       $res  =  $this->execute($requestParam);
       return $res;
    }
   
    /**
     * 获取取消订单
     */
    public function cancelOrder( $params = [] ) 
    {
        if( empty($params['supplierOrder'])) {
            return Normal::returnCode(Normal::FAIL,"except param supplierOrder ");
        }
        //组装订单参数
        $orderInfo = $params['supplierOrder'];
        $order     = $params['order'];
        $data = [
            'OrderNo'   => $orderInfo['supplier_dsn'],
            'Reason '   => $order['exceptReason'] ? $order['exceptReason'] : "人工运营处理售后退款",
        ];

        $requestParam = [
            'method'    => 'cancelOrder',
            'data'      => [
                'companyCode'   => $this->config["companyCode"],
                'msgType'       => "CancelOrder",
                'data'          => json_encode($data,JSON_UNESCAPED_UNICODE),
                'CheckCode'     => $this->getSign($data),
            ]
        ];
        return $this->execute($requestParam);
    }
    
    /**
     * 加签
     * @param array $param
     */
    protected function getSign( array $param = [] )
    {
        //先把报文与密钥前后连接,把连接后的字符串做MD5编码,把MD5编码后的数据进行Base64编码,即为校验码
        $string = json_encode($param,JSON_UNESCAPED_UNICODE);
        $string = md5($string.$this->config["secretkey"],true);
        $sign   = base64_encode($string);
        return $sign;
    }
    
    /**
     * CURL请求
     * @param $params
     * @return mixed
     */
    public function execute( $param = [] )  
    {
        if( empty($param['data']) ) {
            return Normal::returnCode(Normal::FAIL,"数据不能为空");
        }
        $url = $this->config['baseurl'];
        $parameter = [
            [
                'tag'       => $this->account.'_'.$param['method'],
                'uid'       => IdService::instance()->getOtherID(),
                'url'       => $url,
                'data'      => $param['data'],
                'method'    => 'post',
                'format'    => 'json',
                'header'    => [
                    "Content-type:application/json; charset=utf-8",
                ],
        
            ],
        ];
        $resTask = TaskWorker::instance()->addTask($parameter);
        $resTask = current($resTask);
        $res     = $resTask['response']['result'];
        $resHttp = json_decode($res,true);
        if( isset($resHttp['success']) && $resHttp['success'] == true) {
            return Normal::returnCode(Normal::SUC,"请求成功",$resHttp);
        }
        $message = isset($resHttp['msg']) ? $resHttp['msg'] : '请求失败';
        return Normal::returnCode(Normal::FAIL,$message);
    }
}